package reign.network.client;

import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.UUID;

import reign.engine.Message;
import reign.engine.exceptions.ConnectionReconnectedException;
import reign.engine.exceptions.RecievedNonMessageException;
import reign.network.user.NetworkUser;
import reign.network.user.User;
import reign.network.user.User.userType;

public class Session extends Thread{

	private String hostname;
	private int port;
	private String username;
	private String password;
	private Socket conx;
	private boolean stop;
	
	
	public static void main(String [] args)
	{
		Session temp = new Session("tpavlu","password","localhost",8090);
		temp.connect();
	}
	
	public Session(String user,String pass,String host,int portNum)
	{
		hostname = host;
		port = portNum;
		username = user;
		password = pass;
	}
	
	public void start()
	{
		super.start();
		stop = false;
	}
	
	public void stopSession()
	{
		if(this.isAlive())
		{
			stop = true;
		}
	}
	
	public void run()
	{
		while(!stop)
		{
			
		}
	}
	
	public boolean connect()
	{
		try {
			conx = new Socket(hostname,port);
			User me = new User(UUID.randomUUID(), username, password, null);
			ObjectOutputStream oos = new ObjectOutputStream(conx.getOutputStream());
		    // write the objects to the output stream
		    oos.writeObject(me);
		    oos.flush();
			return true;
		} catch (UnknownHostException e) {
			return false;
		} catch (IOException e) {
			return false;
		}
	}
	
	public boolean connect(String host,int portNum)
	{
		hostname = host;
		port = portNum;
		try {
			Socket conx = new Socket(hostname,port);
			User me = new User(UUID.randomUUID(), hostname, hostname, null);
			ObjectOutputStream oos = new ObjectOutputStream(conx.getOutputStream());
		    // write the objects to the output stream
		    oos.writeObject(me);
		    oos.flush();
			return true;
		} catch (UnknownHostException e) {
			return false;
		} catch (IOException e) {
			return false;
		}
	}

	public Message getMessage() throws IOException, ConnectionReconnectedException, RecievedNonMessageException {
		 Object in = null;
		try {
			ObjectInputStream ois = new ObjectInputStream(conx.getInputStream());
			in =  ois.readObject();
			if(in.getClass().equals(Message.class))
			{
				return (Message) in;
			}
			throw new RecievedNonMessageException("Recieved Class: " + in.getClass() + " When Expecting Message Type");
		} catch (IOException e) {
			System.err.println("Error getting Conx InputStream for User: " + this.getName());
			reconnect();
		} catch (ClassNotFoundException e) {
			throw new RecievedNonMessageException("Recieved Class: " + in.getClass() + " When Expecting Message Type");
		}
		throw new ConnectionReconnectedException("Connection Was Lost then Found");
	}

	private void reconnect() throws IOException
	{
		// TODO Add reconnect functions
		System.err.println("Here it should try to reconnect");
	}
	
}
